package edu.fsu.cs.SHPE;

import java.io.IOException;
import java.net.ConnectException;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.ArrayList;

import javax.xml.parsers.SAXParser;
import javax.xml.parsers.SAXParserFactory;

import org.xml.sax.Attributes;
import org.xml.sax.InputSource;
import org.xml.sax.SAXException;
import org.xml.sax.XMLReader;
import org.xml.sax.helpers.DefaultHandler;

import android.graphics.drawable.Drawable;
import android.util.Log;

public class VenueContainer extends ArrayList<Venue> {

	private final static String TAG = "SHPE.VenueContainer";
	
	private static final long serialVersionUID = -4384988965208227441L;
	private Venue tmpVenue;
	private String tmpString;

	public VenueContainer(String url) throws ConnectException{
		if(!parseXml(url))
			throw new ConnectException();
	}
	
	
	public Venue getVenueById(long id){
		for(Venue v : this)
			if(v.getId() == id)
				return v;
		
		return null;
	}
	
	
	private boolean parseXml(String url){

		Log.i(TAG, "<" + url + ">");

		try {
			SAXParserFactory spf = SAXParserFactory.newInstance();
			SAXParser sp = spf.newSAXParser();
			XMLReader xr = sp.getXMLReader();

			URL sourceUrl = new URL(url);
			ConferenceXMLHandler conferenceHandler = new ConferenceXMLHandler();
			xr.setContentHandler(conferenceHandler);
			xr.parse(new InputSource(sourceUrl.openStream()));	

		} catch (Exception e) {
			return false;
		}
		
		return true;

	}

	public class ConferenceXMLHandler extends DefaultHandler {

		public void startDocument() throws SAXException {
			Log.i(TAG, "Document processing started");

			tmpVenue = null;
		}


		public void endDocument() throws SAXException {
			Log.i(TAG, "Document processing finished");

			if(tmpVenue != null)
				add(tmpVenue);
		}


		public void startElement(String uri, String localName, String qName, Attributes attributes){
			Log.i(TAG, "in element " + localName + " qName " + qName + " uri " + uri);


			if(localName.equalsIgnoreCase("conference-venue")){

				if(tmpVenue != null)
					add(tmpVenue);
				
				tmpVenue = null;
				tmpVenue = new Venue();
		
				if(attributes.getValue("name") != null)
					tmpVenue.setName(attributes.getValue("name"));

				tmpVenue.setId(Long.parseLong(attributes.getValue("id")));
				
				if(attributes.getValue("xlink:thumbnail") != null){
					URL src;
					try {
						src = new URL(attributes.getValue("xlink:thumbnail"));
						tmpVenue.setThumbnail(Drawable.createFromStream(src.openStream(), "thumbnail"));
					} catch (MalformedURLException e) {
						// TODO Auto-generated catch block
						e.printStackTrace();
					} catch (IOException e) {
						// TODO Auto-generated catch block
						e.printStackTrace();
					}
				}
				
			}
			else if(tmpVenue != null){
				
				if(localName.equalsIgnoreCase("venue-type"))
					tmpVenue.setVenueTypeId(Long.parseLong(attributes.getValue("id")));
				if(localName.equalsIgnoreCase("coordinate")){
					tmpVenue.setLat(attributes.getValue("lat"));
					tmpVenue.setLon(attributes.getValue("lon"));
				}
				
			}
		}

		public void characters(char[] ch, int start, int length) throws SAXException{
			tmpString = new String(ch, start, length);
			Log.i(TAG, "string " + tmpString);
		}

		public void endElement(String uri, String localName, String qName)
		throws SAXException {
			Log.i(TAG, "endElement " + localName);

			if(localName == null || tmpString == null || tmpVenue == null)
				return;


			if(localName.equalsIgnoreCase("description"))
				tmpVenue.setDescription(tmpString);
			else if(localName.equalsIgnoreCase("website"))
				tmpVenue.setWebsite(tmpString);
			else if(localName.equalsIgnoreCase("phone"))
				tmpVenue.setPhone(tmpString);
			else if(localName.equalsIgnoreCase("address"))
				tmpVenue.setAddress(tmpString);
			else if(localName.equalsIgnoreCase("city"))
				tmpVenue.setCity(tmpString);
			else if(localName.equalsIgnoreCase("province"))
				tmpVenue.setProvince(tmpString);
			else if(localName.equalsIgnoreCase("country"))
				tmpVenue.setCountry(tmpString);
			else if(localName.equalsIgnoreCase("postalCode"))
				tmpVenue.setPostalCode(tmpString);
		}

	}

}
